# -*- coding: utf-8 -*-
"""
Tencent is pleased to support the open source community by making 蓝鲸智云PaaS平台社区版 (BlueKing PaaS Community
Edition) available.
Copyright (C) 2017-2020 THL A29 Limited, a Tencent company. All rights reserved.
Licensed under the MIT License (the "License"); you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://opensource.org/licenses/MIT
Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on
an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the
specific language governing permissions and limitations under the License.
"""
import time

import requests
from django.conf import settings
from django.contrib.auth import logout
from django.db.models import Count
from django.shortcuts import render
from django.core.paginator import Paginator
from blueapps import account
import json
import os
import uuid
from datetime import datetime, timedelta
from django.db import transaction, connection
from django.http import JsonResponse, HttpResponse, HttpResponseRedirect

# 开发框架中通过中间件默认是需要登录态的，如有不需要登录的，可添加装饰器login_exempt
# 装饰器引入 from blueapps.account.decorators import login_exempt
from blueking.component.shortcuts import get_client_by_request
from compus.models import Offline, UserCenter, MissionStatus, AcceptMission
from compus.tasks import send_mail, create_user
from blueapps.account.components.bk_token.middlewares import LoginRequiredMiddleware
from django.utils.deprecation import MiddlewareMixin


def home(request):
    """
    首页
    """
    create_user.delay(request.user)
    return render(request, "home_application/index_home.html")


def my_mission(request):
    """
    已接单任务
    """
    return render(request, "home_application/mission/my_mission.html")


def my_release(request):
    """
    已发布任务
    """
    return render(request, "home_application/mission/my_release.html")


def release_online(request):
    """
    发布在线任务
    """
    return render(request, "home_application/release/release_online.html")


def release_offline(request):
    """
    发布在线任务
    """
    return render(request, "home_application/release/release_offline.html")


def user_center(request):
    """
    用户中心
    """
    try:
        user = UserCenter.objects.filter(compus_user=request.user)
        result_data = []
        for user_item in user:
            result_data.append(
                {
                    "compus_user": user_item.compus_user.username,
                    "user_sex": user_item.user_sex,
                    "user_phone": user_item.user_phone,
                    "user_remarks": user_item.user_remarks,
                    "user_email": user_item.user_email,
                }
            )
    except Exception:
        return render(request, "home_application/index_home.html")
    return render(request, "home_application/user/user_center.html", {"user": result_data})


def get_offline_mission_list(request):
    """
    获取生效中跑腿任务列表数据
    """
    # 获取操作次数
    draw = int(request.GET.get("draw"))
    # 获取起始位置
    start = int(request.GET.get("start"))
    offline = Offline.objects.filter(effect_time__gte=datetime.now(),
                                     mission_status=MissionStatus.EFFECT)
    total = len(offline)
    page_length = int(request.GET.get("length"))
    page = start / page_length + 1

    paginator = Paginator(offline, page_length)
    offline = paginator.get_page(page)
    result_data = []
    for offline_item in offline:
        result_data.append(
            {
                "id": offline_item.id,
                "belonging_user": offline_item.belonging_user.username,
                "create_time": offline_item.create_time.strftime("%Y-%m-%d %H:%M:%S"),
                "mission_type": offline_item.get_mission_type_display(),
                "mission_require": offline_item.mission_require,
                "effect_time": offline_item.effect_time.strftime("%Y-%m-%d %H:%M:%S"),
                "mission_salary": offline_item.mission_salary,
            }
        )
    obj = ([{'value': 3, 'name': '未执行'}, {'value': 8, 'name': '已执行'}], ['未执行', '已执行'])
    return JsonResponse(
        {
            "result": True, "code": 200,
            "data": {
                "info": {
                    'data': result_data,
                    "recordsTotal": total,
                    "recordsFiltered": total,
                    "draw": draw,
                }
            }
        }
    )


def save_offline_mission_info(request):
    """
    保存跑腿任务信息
    """
    try:
        belonging_user = request.user
        mission_type = int(request.POST.get("mission_type"))
        mission_salary = float(request.POST.get("mission_salary"))
        mission_phone = request.POST.get("mission_phone")
        effect_time = request.POST.get("effect_time")
        mission_require = request.POST.get("mission_require")
        mission_remarks = request.POST.get("mission_remarks")
        kwargs = {
            "belonging_user": belonging_user,
            "mission_type": mission_type,
            "mission_salary": mission_salary,
            "mission_phone": mission_phone,
            "effect_time": effect_time,
            "mission_require": mission_require,
            "mission_remarks": mission_remarks,
        }
        now = str(datetime.now())
        if effect_time < now:
            return JsonResponse({"result": False, "code": 101, "message": "截止时间不能小于当前时间,请刷新后重试"})
    except Exception:
        return JsonResponse({"result": False, "code": 101, "message": "参数获取错误"})
    try:
        with transaction.atomic():
            Offline.objects.create(**kwargs)
    except Exception:
        return JsonResponse({"result": False, "code": 101, "message": "error"})
    return JsonResponse({"result": True, "code": 200, "message": "success"})


def my_release_offline_mission_list(request):
    """
    获取我发布的任务
    """
    # 获取操作次数
    draw = int(request.GET.get("draw"))
    # 获取起始位置
    start = int(request.GET.get("start"))
    offline = Offline.objects.filter(belonging_user=request.user)
    total = len(offline)
    page_length = int(request.GET.get("length"))
    page = start / page_length + 1

    paginator = Paginator(offline, page_length)
    offline = paginator.get_page(page)
    result_data = []
    for my_offline_item in offline:
        result_data.append(
            {
                "id": my_offline_item.id,
                "create_time": my_offline_item.create_time.strftime("%Y-%m-%d %H:%M:%S"),
                "mission_type": my_offline_item.get_mission_type_display(),
                "mission_status": my_offline_item.get_mission_status_display(),
                "mission_require": my_offline_item.mission_require,
                "effect_time": my_offline_item.effect_time.strftime("%Y-%m-%d %H:%M:%S"),
                "mission_salary": my_offline_item.mission_salary,
            }
        )
    return JsonResponse(
        {
            "result": True, "code": 200,
            "data": {
                "info": {
                    'data': result_data,
                    "recordsTotal": total,
                    "recordsFiltered": total,
                    "draw": draw,
                }
            }
        }
    )


def delete_offline_mission_info(request, mission_id):
    """
    删除数据
    """
    try:
        with transaction.atomic():
            offline_mission_obj = Offline.objects.get(id=int(mission_id))
            offline_mission_obj.delete()
    except Exception:
        return JsonResponse({"result": False, "code": 101, "message": "删除数据失败"})
    return JsonResponse(
        {
            "result": True,
            "code": 200,
            "message": "success"
        }
    )


def edit_user_info(request):
    """
    编辑我的信息
    """
    try:
        user_sex = request.POST.get("user_sex")
        user_phone = request.POST.get("user_phone")
        user_remarks = request.POST.get("user_remarks")
        user_email = request.POST.get("user_email")
        kwargs = {
            "user_sex": user_sex,
            "user_phone": user_phone,
            "user_remarks": user_remarks,
            "user_email": user_email,
        }
    except Exception:
        return JsonResponse({"result": False, "code": 101, "message": "参数获取错误"})
    try:
        with transaction.atomic():
            UserCenter.objects.filter(compus_user=request.user).update(**kwargs)
    except Exception:
        return JsonResponse({"result": False, "code": 101, "message": "error"})
    return JsonResponse({"result": True, "code": 200, "message": "success"})


def accept_mission_by_id(request, mission_id):
    """
    接受任务
    """
    try:
        accept_mission = Offline.objects.get(id=int(mission_id))
        accept_mission.mission_status = MissionStatus.ACCEPT
        accept_user = UserCenter.objects.get(compus_user=request.user)
        belong_user = UserCenter.objects.get(compus_user=accept_mission.belonging_user)
        kwargs = {
            "accept_mission": accept_mission,
            "accept_user": accept_user,
        }
        with transaction.atomic():
            AcceptMission.objects.create(**kwargs)
            accept_mission.save()
            if belong_user.user_email:
                receiver = belong_user.user_email
                title = "您发布的任务已被接单啦"
                content = f"<table border=\"0\" cellpadding=\"0\" cellspacing=\"0\" width=\"100%\"><tbody><tr><td style=\"padding:0 30px; line-height:24px;text-align:left;\">" \
                          f"<tr><td style=\"padding:0 30px; line-height:24px;text-align:left;\">您的'{accept_mission.get_mission_type_display()}'订单已经被用户'{accept_user.compus_user.username}'接单啦</td></tr>" \
                          f"<tr><td style=\"padding:0 30px; line-height:24px;text-align:left;\">联系电话：{accept_user.user_phone}</td></tr>" \
                          f"<tr><td style=\"padding:0 30px; line-height:24px;text-align:left;\">用户个人备注：{accept_user.user_remarks}</td></tr>" \
                          f"</tbody></table>"
                client = get_client_by_request(request)
                send_mail.delay(client, receiver, title, content, int(mission_id))
    except Exception:
        return JsonResponse({"result": False, "code": 101, "message": "error"})
    return JsonResponse({"result": True, "code": 200, "message": "success"})


def my_offline_mission_list(request):
    """
    获取我接受的任务
    """
    # 获取操作次数
    draw = int(request.GET.get("draw"))
    # 获取起始位置
    start = int(request.GET.get("start"))
    myMission = AcceptMission.objects.filter(accept_user__compus_user=request.user)
    total = len(myMission)
    page_length = int(request.GET.get("length"))
    page = start / page_length + 1

    paginator = Paginator(myMission, page_length)
    myMission = paginator.get_page(page)
    result_data = []
    for my_offline_item in myMission:
        mission = Offline.objects.get(id=my_offline_item.accept_mission.id)
        result_data.append(
            {
                "mission_id": mission.id,
                "id": my_offline_item.id,
                "belonging_user": mission.belonging_user.username,
                "create_time": mission.create_time.strftime("%Y-%m-%d %H:%M:%S"),
                "mission_type": mission.get_mission_type_display(),
                "mission_status": mission.get_mission_status_display(),
                "mission_require": mission.mission_require,
                # "mission_remarks": mission.mission_remarks,
                "effect_time": mission.effect_time.strftime("%Y-%m-%d %H:%M:%S"),
                # "mission_salary": mission.mission_salary,
            }
        )
    return JsonResponse(
        {
            "result": True, "code": 200,
            "data": {
                "info": {
                    'data': result_data,
                    "recordsTotal": total,
                    "recordsFiltered": total,
                    "draw": draw,
                }
            }
        }
    )


def cancel_mission_by_id(request, accept_id):
    """
    取消任务
    """
    try:
        accept_mission = AcceptMission.objects.get(id=int(accept_id))
        mission = Offline.objects.get(id=accept_mission.accept_mission.id)
    except Exception:
        return JsonResponse({"result": False, "code": 101, "message": "参数获取错误"})
    try:
        with transaction.atomic():
            accept_mission.delete()
            mission.mission_status = MissionStatus.CANCEL
            mission.save()
    except Exception:
        return JsonResponse({"result": False, "code": 101, "message": "error"})
    return JsonResponse({"result": True, "code": 200, "message": "success"})


def republish_mission(request, mission_id):
    try:
        mission = Offline.objects.get(id=int(mission_id))
        mission.mission_status = MissionStatus.EFFECT
        mission.save()
    except Exception:
        return JsonResponse({"result": False, "code": 101, "message": "error"})
    return JsonResponse({"result": True, "code": 200, "message": "success"})


SAVE_DIR = "./static/file"


def finish_mission(request):
    """
    完成任务
    """
    accept_mission_id = request.POST.get("mission_id", "")
    remark = request.POST.get("remark", None)
    file_obj = request.FILES.get("file", None)
    if not remark:
        return JsonResponse({"result": False, "code": 101, "message": "请填写完成情况"})
    if not file_obj:
        return JsonResponse({"result": False, "code": 101, "message": "请上传附件"})
    if not accept_mission_id:
        return JsonResponse({"result": False, "code": 101, "message": "参数错误"})
    if file_obj.name.split(".") == 0 or file_obj.name.split(".") == 1:
        return JsonResponse({"result": False, "code": 101, "message": "⽂件名错误，⽆扩展名称或⽆⽂件名称"})
    if not os.path.exists(SAVE_DIR):
        os.makedirs(SAVE_DIR)
    new_file_name = "{}.{}".format(str(uuid.uuid4()), ".".join(file_obj.name.split(".")[1:]))
    if file_obj:
        with open(os.path.join(SAVE_DIR, new_file_name), 'wb') as w:
            for block in file_obj.chunks():
                w.write(block)
    file_url = str(os.path.join(SAVE_DIR, new_file_name))
    kwargs = {}
    kwargs.update({
        "attachment_name": file_obj.name,
        "attachment_url": file_url,
        "remark": remark,
    })
    try:
        with transaction.atomic():
            AcceptMission.objects.filter(id=accept_mission_id).update(**kwargs)
            mission_obj = AcceptMission.objects.get(id=accept_mission_id)
            mission = Offline.objects.get(id=mission_obj.accept_mission.id)
            mission.mission_status = MissionStatus.CHECK
            mission.save()
    except Exception:
        return JsonResponse({"result": False, "code": 101, "message": "保存失败"})
    return JsonResponse({"result": True, "code": 200, "message": "success", "data": {}})


def display_finish_mission_by_id(request, mission_id):
    """
    获取审核数据
    """
    try:
        mission = Offline.objects.get(id=int(mission_id))
        accept_mission = AcceptMission.objects.get(accept_mission=mission)
        return JsonResponse(
            {
                "result": True, "code": 200,
                "data": {
                    "info": {
                        'data': {
                            "remark": accept_mission.remark,
                            "attachment_url": accept_mission.attachment_url,
                        }
                    }
                }
            }
        )
    except Exception:
        return JsonResponse({"result": False, "code": 101, "message": "获取数据失败"})


def pass_check_mission(request):
    mission_id = request.POST.get("mission_id", "")
    comment = request.POST.get("comment", "")
    kwargs = {}
    kwargs.update({
        "comment": comment,
    })
    try:
        mission = Offline.objects.get(id=int(mission_id))
        mission.mission_status = MissionStatus.FINISH
        with transaction.atomic():
            mission.save()
            AcceptMission.objects.filter(accept_mission=mission).update(**kwargs)
    except Exception:
        return JsonResponse({"result": False, "code": 101, "message": "保存失败"})
    return JsonResponse({"result": True, "code": 200, "message": "success", "data": {}})


def get_accept_mission_by_id(request, mission_id):
    """
    获取订单信息
    """
    try:
        mission = Offline.objects.get(id=int(mission_id))
        accept_mission = AcceptMission.objects.get(accept_mission=mission)
        accept_user = UserCenter.objects.get(id=accept_mission.accept_user.id)
        return JsonResponse(
            {
                "result": True, "code": 200,
                "data": {
                    "info": {
                        'data': {
                            "accept_user": accept_mission.accept_user.compus_user.username,
                            "user_phone": accept_user.user_phone,
                            "user_remarks": accept_user.user_remarks,
                            "create_time": accept_mission.create_time.strftime("%Y-%m-%d %H:%M:%S"),
                            "remark": accept_mission.remark,
                            "attachment_url": accept_mission.attachment_url,
                            "comment": accept_mission.comment,
                        }
                    }
                }
            }
        )
    except Exception:
        return JsonResponse({"result": False, "code": 101, "message": "获取数据失败"})


def get_belong_user_info_by_id(request, mission_id):
    try:
        mission = Offline.objects.get(id=int(mission_id))
        user = UserCenter.objects.get(compus_user=mission.belonging_user)
        return JsonResponse(
            {
                "result": True, "code": 200,
                "data": {
                    "info": {
                        'data': {
                            "belonging_user": user.compus_user.username,
                            "user_phone": user.user_phone,
                            "user_remarks": user.user_remarks,
                            "mission_remarks": mission.mission_remarks,
                            "mission_salary": mission.mission_salary,
                        }
                    }
                }
            }
        )
    except Exception:
        return JsonResponse({"result": False, "code": 101, "message": "获取数据失败"})


def get_pie(request):
    count = Offline.objects.filter(effect_time__gte=datetime.now(),
                                   mission_status=MissionStatus.EFFECT).values('mission_type').order_by(
        'mission_type').annotate(nums=Count('*'))
    count = list(count)
    value = [0, 0, 0, 0, 0, 0]
    for i in range(len(count)):
        tmp = list(count[i].values())
        value[int(tmp[0])] = tmp[1]
    return JsonResponse(
        {
            "code": 0,
            "result": True,
            "message": "success",
            "data": {
                "title": "",
                "series": [{
                    "value": value[0],
                    "name": "其他"
                }, {
                    "value": value[1],
                    "name": "取外卖"
                }, {
                    "value": value[2],
                    "name": "取快递"

                }, {
                    "value": value[3],
                    "name": "跑腿"

                }, {
                    "value": value[4],
                    "name": "打印"
                }]
            }
        }
    )


def get_chart(request):
    select = {'day': connection.ops.date_trunc_sql('day', 'create_time')}
    today = datetime.now() + timedelta(days=1)
    weekdelta = datetime.now().date() - timedelta(weeks=1)
    count_data = Offline.objects.filter(create_time__gte=weekdelta, create_time__lte=today).extra(select=select).values(
        'day').order_by('-create_time__day').annotate(number=Count('*'))

    begin_date = (datetime.now() - timedelta(days=6)).strftime("%Y-%m-%d")
    date_list = []
    begin_date = datetime.strptime(begin_date, "%Y-%m-%d")
    end_date = datetime.strptime(time.strftime('%Y-%m-%d', time.localtime(time.time())), "%Y-%m-%d")
    while begin_date <= end_date:
        date_str = begin_date.strftime("%m-%d")
        date_list.append(date_str)
        begin_date += timedelta(days=1)

    x_list = []
    y_list = []
    result1 = [0, 0, 0, 0, 0, 0, 0]
    for i in count_data:
        tmp = i['day'].strftime('%m-%d')
        x_list.append(tmp)
        y_list.append(i['number'])
    for j in range(len(x_list)):
        for k in range(7):
            if x_list[j] == date_list[k]:
                result1[k] = y_list[j]

    x_list = []
    y_list = []
    result2 = [0, 0, 0, 0, 0, 0, 0]
    count_data = AcceptMission.objects.filter(create_time__gte=weekdelta, create_time__lte=today).extra(select=select).values(
        'day').order_by('-create_time__day').annotate(number=Count('*'))
    for i in count_data:
        tmp = i['day'].strftime('%m-%d')
        x_list.append(tmp)
        y_list.append(i['number'])
    for j in range(len(x_list)):
        for k in range(7):
            if x_list[j] == date_list[k]:
                result2[k] = y_list[j]
    return JsonResponse(
        {
            "code": 0,
            "result": True,
            "messge": "success",
            "data": {
                "xAxis": date_list,
                "series": [
                    {
                        "name": "发布量",
                        "type": "line",
                        "data": result1
                    },
                    {
                        "name": "接单量",
                        "type": "line",
                        "data": result2
                    }
                ]
            }
        }
    )
